import inner.Body;
import inner.MyInterface;
import inner.Outer;

/**
    如果一个事物的内部包含另一个事物，那么这就是一个类内部包含另一个类。
    例如：身体和心脏的关系。又如：汽车和发动机的关系。

    分类：
     1. 成员内部类
     2. 局部内部类（包含匿名内部类）

    成员内部类:
     1.外部类调用内部类需要:创建内部类对象.调用
     2.内部类可以随意调用外部类成员变量及函数;
     3.内外部类变量重名是采用就近原则;

    局部内部类:
     1.“局部”：只有当前所属的方法才能使用它，出了这个方法外面就不能用了。

    匿名内部类:
    如果接口的实现类（或父类的子类）只使用一次，那么这种情况下可以改为使用【匿名内部类】。
    强调：匿名内部类和匿名对象不是一回事！！！

 */
public class Demo03InnerClass {
    public static void main(String[] args) {

        /*------成员内部类-------------------*/
        Body body = new Body();  // 外部类的对象
        body.methodBody();        //外部类调用方法,方法内调用内部类方法Heart
        System.out.println("=====================");

        // 按照公式写：
        Body.Heart heart = new Body().new Heart();
        heart.beat();

        /*------局部内部类-------------------*/
        Outer obj = new Outer();
        obj.methodOuter();

        /*------匿名内部类-------------------*/
        //只用了一次
//        MyInterface obj = new MyInterfaceImpl();
//        obj.method();

//        MyInterface some = new MyInterface(); // 接口不允许创建,错误写法！

        // 要使用匿名内部类，这种是创建匿名对象，对象名称就叫objA
        MyInterface objA = new MyInterface() {
            @Override
            public void method1() {
                System.out.println("匿名内部类实现了方法！111-A");
            }

            @Override
            public void method2() {
                System.out.println("匿名内部类实现了方法！222-A");
            }
        };
        objA.method1();
        objA.method2();
        System.out.println("---------------------------------------");

        // 使用了匿名内部类，而且省略了对象名称，也是匿名对象
        new MyInterface() {
            @Override
            public void method1() {
                System.out.println("匿名内部类实现了方法！111-B");
            }

            @Override
            public void method2() {
                System.out.println("匿名内部类实现了方法！222-B");
            }
        }.method1();

    }
}

